﻿/*
using System;
using Microsoft.Xna.Framework;
using System.Collections.Generic;
using Microsoft.Xna.Framework.Graphics;
namespace Dragoon
{
    interface IGeometryBuilder
    {
        void AddCube(Microsoft.Xna.Framework.Vector3 center, float width, float length, float thickness);
        void AddCube(Microsoft.Xna.Framework.Vector3 center, Vector3 sizeLengths);
        void AddCube(Microsoft.Xna.Framework.Vector3 center, float size);
        void AddQuadrangle(Microsoft.Xna.Framework.Vector3 center, float width, float length);
        void AddQuadrangle(Microsoft.Xna.Framework.Vector3 p1, Microsoft.Xna.Framework.Vector3 p2, Microsoft.Xna.Framework.Vector3 p3, Microsoft.Xna.Framework.Vector3 p4);
        void AddTriangle(Microsoft.Xna.Framework.Vector3 p1, Microsoft.Xna.Framework.Vector3 p2, Microsoft.Xna.Framework.Vector3 p3);
        void AddPipe(Vector3 from, Vector3 to, float radius, int segments);
    }


    class GeometryBuilder<vertexT> : IGeometryBuilder
    where vertexT : struct
    {
        public delegate vertexT BuildVertex(Vector3 v, Vector3 normal);
        private readonly BuildVertex _buildFromVector;
        List<vertexT> _points = new List<vertexT>();
        List<short> _indexSequence = new List<short>();

        public GeometryBuilder(BuildVertex vertexBuilder)
        {
            if (vertexBuilder == null)
                throw new ArgumentNullException("vertexBuilder");
            _buildFromVector = vertexBuilder;
        }


        private short IndexOf(vertexT p)
        {
            int index = _points.IndexOf(p);
            if (index > -1)
                return (short)index;

            if (_points.Count == short.MaxValue)
                throw new Exception("Too many points in Geometry");

            _points.Add(p);
            return (short)(_points.Count - 1);
        }

        private short IndexOf(Vector3 v, Vector3 n)
        {
            return IndexOf(_buildFromVector(v, n));
        }

        /// <summary>
        /// sequence clockwise on visible plane
        /// </summary>
        /// <param name="p1"></param>
        /// <param name="p2"></param>
        /// <param name="p3"></param>
        public void AddTriangle(Vector3 p1, Vector3 p2, Vector3 p3)
        {
            Vector3 r1 = p2 - p1;
            Vector3 r2 = p3 - p2;
            Vector3 n = Vector3.Cross(r2, r1) * -1.0f;
            n.Normalize();
            _indexSequence.Add(IndexOf(p3, n));
            _indexSequence.Add(IndexOf(p2, n));
            _indexSequence.Add(IndexOf(p1, n));
        }

        /// <summary>
        /// sequence clockwise on visible plane
        /// </summary>
        /// <param name="p1"></param>
        /// <param name="p2"></param>
        /// <param name="p3"></param>
        /// <param name="p4"></param>
        public void AddQuadrangle(Vector3 p1, Vector3 p2, Vector3 p3, Vector3 p4)
        {
            AddTriangle(p1, p2, p3);
            AddTriangle(p3, p4, p1);
        }


        public void AddQuadrangle(Vector3 center, float width, float length)
        {
            Vector3 c1 = new Vector3(center.X - width / 2.0F, center.Y + length / 2.0F, center.Z);
            Vector3 c2 = c1 + Vector3.Right * width;
            Vector3 c3 = c2 + Vector3.Forward * length;
            Vector3 c4 = c3 + Vector3.Left * width;
            AddQuadrangle(c1, c2, c3, c4);
        }

        public void Clear()
        {
            _points.Clear();
            _indexSequence.Clear();
        }

        public void AddCube(Vector3 center, float size)
        {
            AddCube(center, size, size, size);
        }


        public Geometry<vertexT> MakeGeometry(GraphicsDevice device, int sizeOfVertex, VertexElement[] elements)
        {
            return new Geometry<vertexT>(device, sizeOfVertex, elements, _indexSequence.ToArray(), _points.ToArray());
        }

        public void AddCube(Vector3 center, float width, float length, float thickness)
        {
            Vector3 c1 = center
                         + Vector3.Left * (width / 2.0F)
                         + Vector3.Backward * (length / 2.0F)
                         + Vector3.Up * (thickness / 2.0f);
            Vector3 c2 = c1 + Vector3.Right * width;
            Vector3 c3 = c2 + Vector3.Forward * length;
            Vector3 c4 = c3 + Vector3.Left * width;
            Vector3 c5 = c1 + Vector3.Down * thickness;
            Vector3 c6 = c2 + Vector3.Down * thickness;
            Vector3 c7 = c3 + Vector3.Down * thickness;
            Vector3 c8 = c4 + Vector3.Down * thickness;
            AddQuadrangle(c1, c2, c3, c4); // top
            AddQuadrangle(c1, c4, c8, c5); // left
            AddQuadrangle(c5, c8, c7, c6); // bottom
            AddQuadrangle(c3, c2, c6, c7); // right            
            AddQuadrangle(c4, c3, c7, c8); // front
            AddQuadrangle(c1, c5, c6, c2); // back
        }

        public void AddCube(Vector3 center, Vector3 sideLengths)
        {
            AddCube(center, sideLengths.X, sideLengths.Z, sideLengths.Y);
        }

        public void AddPipe(Vector3 from, Vector3 to, float radius, int segments)
        {
            Vector3 dir = to - from;
            float distance = dir.Length();
            dir.Normalize();
            float incAngle = -MathHelper.Pi * 2.0f / segments;
            float atAngle = MathHelper.PiOver4; // rotate 45 deg
            Vector3[] fromPoints = new Vector3[segments];
            Vector3[] toPoints = new Vector3[segments];
            Matrix transform;
            Vector3 startPoint = Vector3.Up * radius;
            for (int i = 0; i < segments; i++)
            {
                Vector3 p = new Vector3(radius, 0, 0);
                transform =
                    Matrix.CreateTranslation(startPoint)
                    * Matrix.CreateFromAxisAngle(dir, atAngle)
                    * Matrix.CreateTranslation(from);
                fromPoints[i] = transform.Translation;
                transform =
                    Matrix.CreateTranslation(startPoint)
                    * Matrix.CreateFromAxisAngle(dir, atAngle)
                    * Matrix.CreateTranslation(to);
                toPoints[i] = transform.Translation; 
                atAngle +=  incAngle;
            }
            Vector3 p1, p2, p3, p4;
            for (int i = 0; i < segments; i++)
            {
                p1 = fromPoints[i];
                p2 = toPoints[i];
                if (i+1 == segments)
                {
                    p3 = toPoints[0];
                    p4 = fromPoints[0];
                }
                else
                {
                    p3 = toPoints[i + 1];
                    p4 = fromPoints[i + 1];
                }
                AddQuadrangle(p1, p2, p3, p4);
                AddTriangle(p1, p4, from);
                AddTriangle(p3, p2, to);
            }
            
        }
    }

}
*/